#ifndef __GPIO_H__
#define __GPIO_H__
#ifdef __cplusplus
extern "C" {
#endif
#include "target.h"
#include <stdint.h>

#define GPIO_DEVICE "/dev/gpio"

#define GPIO_READ 0x02
#define GPIO_WRITE 0x41

#define RALINK_GPIO_SET_DIR     0x01
#define RALINK_GPIO_SET_DIR_IN      0x11
#define RALINK_GPIO_SET_DIR_OUT     0x12
#define RALINK_GPIO_READ        0x02
#define RALINK_GPIO_WRITE       0x03
#define RALINK_GPIO_SET         0x21
#define RALINK_GPIO_CLEAR       0x31

#ifdef MT7620
#define RALINK_GPIO3924_SET_DIR     0x51
#define RALINK_GPIO3924_SET_DIR_IN  0x13
#define RALINK_GPIO3924_SET_DIR_OUT 0x14
#define RALINK_GPIO3924_READ        0x52
#define RALINK_GPIO3924_WRITE       0x53
#define RALINK_GPIO3924_SET         0x22
#define RALINK_GPIO3924_CLEAR       0x32

#define RALINK_GPIO7140_SET_DIR     0x61
#define RALINK_GPIO7140_SET_DIR_IN  0x15
#define RALINK_GPIO7140_SET_DIR_OUT 0x16
#define RALINK_GPIO7140_READ        0x62
#define RALINK_GPIO7140_WRITE       0x63
#define RALINK_GPIO7140_SET     0x23
#define RALINK_GPIO7140_CLEAR       0x33

#define RALINK_GPIO72_SET_DIR       0x71
#define RALINK_GPIO72_SET_DIR_IN    0x17
#define RALINK_GPIO72_SET_DIR_OUT   0x18
#define RALINK_GPIO72_READ      0x72
#define RALINK_GPIO72_WRITE     0x73
#define RALINK_GPIO72_SET       0x24
#define RALINK_GPIO72_CLEAR     0x34

#elif defined(MT7621) 
#define	RALINK_GPIO6332_SET_DIR		0x51
#define RALINK_GPIO6332_SET_DIR_IN	0x13
#define RALINK_GPIO6332_SET_DIR_OUT	0x14
#define	RALINK_GPIO6332_READ		0x52
#define	RALINK_GPIO6332_WRITE		0x53
#define	RALINK_GPIO6332_SET		0x22
#define	RALINK_GPIO6332_CLEAR		0x32

#define	RALINK_GPIO9564_SET_DIR		0x61
#define RALINK_GPIO9564_SET_DIR_IN	0x15
#define RALINK_GPIO9564_SET_DIR_OUT	0x16
#define	RALINK_GPIO9564_READ		0x62
#define	RALINK_GPIO9564_WRITE		0x63
#define	RALINK_GPIO9564_SET		0x23
#define	RALINK_GPIO9564_CLEAR		0x33

#elif defined(IMX6UL)
#define GPIO_U_IOCTL_READ_BASE 'r'
#define GPIO_U_IOCTL_IN_BASE 'i'
#define GPIO_U_IOCTL_OUT_BASE 'o'
#define GPIOC_OPS_OUT   _IOWR(GPIO_U_IOCTL_OUT_BASE,0,int)
#define GPIOC_OPS_IN   _IOWR(GPIO_U_IOCTL_IN_BASE,0,int)
#define GPIOC_OPS_READ   _IOWR(GPIO_U_IOCTL_READ_BASE,0,int)
#else
#error "No target has defined"
#endif

enum {
	GPIO_OFF,
	GPIO_ON,
	GPIO_BLINK,
};

enum {
	GPIO_OK,
	GPIO_FAIL,
};

#if defined(MT7620)
#define GPIO_LED_SIGA			69
#define GPIO_LED_SIGB			68
#define GPIO_LED_SIGC			67
#define GPIO_LED_ONLINE			70
#define GPIO_LED_ALARM			71
#define GPIO_LED_WIFI_2G		72
#define GPIO_POWER_DONGLE		27
#define GPIO_RESET				22

#elif defined(MT7621)
#define GPIO_LED_SIGA			36
#define GPIO_LED_SIGB			35
#define GPIO_LED_SIGC			34
#define GPIO_LED_ONLINE			37
#define GPIO_LED_ALARM			38
#define GPIO_LED_WIFI_2G		40
#define GPIO_POWER_DONGLE		10
#define GPIO_POWER_SFP			12
#define GPIO_RESET				18

#elif defined(IMX6UL)
#define GPIO(n,x)       ((n-1)*32 + x)

#ifdef TARGET_TG462
#define I2C_GPIO_DEV			"/dev/priv/pcal6416"
#define I2C_ADC_DEV				"/dev/priv/ms1112"
#define GPIO_LED_SIGC			1000
#define GPIO_LED_SIGB			1001
#define GPIO_LED_SIGA			1002
#define GPIO_LED_WIFI_2G		1003
#define GPIO_LED_GPS			1004
#define GPIO_LED_ONLINE			1005
#define GPIO_LED_ALARM			-1
#define GPIO_POWER_DONGLE		GPIO(1, 22)
#define GPIO_POWER_WIFI			GPIO(1, 19)
#define GPIO_POWER_GPS			GPIO(1, 10)
#define GPIO_POWER_ADC			GPIO(1, 15)
#define GPIO_POWER_SD			GPIO(5, 8)
#define GPIO_POWER_VCC_OUT		GPIO(4, 21) /*output 12V */
#define GPIO_POWER_VCC_9V_OUT	GPIO(4, 22)
#define GPIO_POWER_VCC_5V_OUT	GPIO(4, 23)
#define GPIO_POWER_SHT10		GPIO(4, 24)
#define GPIO_POWER_BMP180		GPIO(5, 0)
#define GPIO_POWER_LCD			GPIO(5, 1)
#define GPIO_RELAY1				GPIO(1, 13)
#define GPIO_RELAY2				GPIO(1, 11)
#define GPIO_RELAY3				GPIO(1, 12)
#define GPIO_RELAY4				GPIO(1, 14)
#define GPIO_DI1				GPIO(4, 28)
#define GPIO_DI2				GPIO(4, 27)
#define GPIO_DI3				GPIO(4, 26)
#define GPIO_DI4				GPIO(4, 25)
#define GPIO_RESET				18
#define GPIO_POWER_SIM_SWITCH	-1

#else  /* define for TG452 */
#define GPIO_LED_SIGA			GPIO(3, 18)
#define GPIO_LED_SIGB			GPIO(3, 19)
#define GPIO_LED_SIGC			GPIO(3, 20)
#define GPIO_LED_ONLINE			GPIO(3, 17)
#define GPIO_LED_SIGA2			GPIO(3, 6)
#define GPIO_LED_SIGB2			GPIO(3, 7)
#define GPIO_LED_SIGC2			GPIO(3, 15)
#define GPIO_LED_ONLINE2		GPIO(3, 5)
#define GPIO_LED_ALARM			GPIO(4, 23)
#define GPIO_LED_WIFI_2G		GPIO(4, 22)
#define GPIO_POWER_DONGLE		GPIO(1, 22)
#define GPIO_POWER_DONGLE2		GPIO(1, 10)
#define GPIO_POWER_WIFI			GPIO(1, 19)
#define GPIO_POWER_ADC			GPIO(1, 15)
#define GPIO_POWER_SD			GPIO(5, 8)
#define GPIO_POWER_VCC_OUT		GPIO(4, 21)
#define GPIO_POWER_SIM_SWITCH	GPIO(4, 25)
#define GPIO_RELAY1				GPIO(1, 14)
#define GPIO_RELAY2				GPIO(1, 11)
#define GPIO_DI1				GPIO(4, 28)
#define GPIO_DI2				GPIO(4, 27)
#define GPIO_DI3				GPIO(4, 26)
#define GPIO_DI4				GPIO(4, 25)
#define GPIO_RESET				18

#endif /* end of TARGET_TG462 */

#else
#define GPIO_LED_SIGA			69
#define GPIO_LED_SIGB			68
#define GPIO_LED_SIGC			67
#define GPIO_LED_ONLINE			70
#define GPIO_LED_ALARM			71
#define GPIO_LED_WIFI_2G		72
#define GPIO_POWER_DONGLE		27
#define GPIO_RESET				28

#endif /* end of MT7620 */

enum {
	DIR_IN,
	DIR_OUT,
};

enum {
	LED_MODE,
	POWER_MODE,
};

enum {
	LED_OFF,
	LED_ON,
	LED_BLINK_FAST,
	LED_BLINK_SLOW,   /* 1 second on, 1 second off */
	LED_BLINK_NORMAL, /* 0.5 second on, 0.5 second off */
	LED_BLINK_STOP,
};

int set_gpio_val(unsigned int gpio, unsigned int val);

int get_gpio_val(unsigned int gpio, unsigned int *val);

int set_gpio_dir(unsigned int gpio, unsigned int dir);

int gpio_set_val(unsigned int gpio, unsigned int val);

int gpio_get_val(unsigned int gpio, unsigned int *val);

int gpio_set_dir(unsigned int gpio, unsigned int dir);

#define GPIO_UNUSED 0

#if defined(IMX6UL)
#ifdef TARGET_TG462
#define MS1112_CNTL_ADC_PATH   "/dev/priv/ms1112"
#define PCAL6416_CNTL_LED_PATH "/dev/priv/pcal6416"
#define BMP180_CNTL_PATH	   "/dev/priv/bmp180"
#define SHT10_CNTL_PATH		   "/dev/priv/sht10"

typedef struct _atmos{
	int temperature;	//unit = 0.1C
	int pressure;   	//unit = Pa
} atmos_t;

typedef struct _sht10{
	int humidity;   	//unit = mRH
	int temperature;	//unit = mC
} sht10_t;

int get_humidity_temperature(sht10_t *value);
int get_pressure_temperature(atmos_t *value);
#endif
int export_gpio(int gpio);
int gpio_trigger_edge(int gpio, int type);
int read_adc_raw(int adc_num);
int get_di_value(int gpio, unsigned int *val);

#ifdef __cplusplus
}
#endif

#endif

#endif /* end of __GPIO_H__ */
